/*
This file is part of MMM.

MMM is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.

MMM is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
GNU General Public License for more details.

You should have received a copy of the GNU General Public License
along with MMM.  If not, see <http://www.gnu.org/licenses/>.
*
* @package    MMM
* @author     Nikolaus Vahrenkamp
* @copyright  2013 High Performance Humanoid Technologies (H2T), Karlsruhe, Germany
*
*/

#ifndef __MMM_MarkerBasedConverter_H_
#define __MMM_MarkerBasedConverter_H_

#include "../../../MMMCore.h"
#include <Eigen/Core>
#include <string> 
#include <vector>
#include <map>

#include "../../../MMMImportExport.h"
#include "../AbstractMotion.h"
#include "../MarkerMotion.h"
#include "../../../Model/Model.h"
#include "Converter.h"

// using forward declarations here, so that the rapidXML header does not have to be parsed when this file is included
namespace rapidxml
{
    template<class Ch>
    class xml_node;
}

namespace MMM
{


/*!
	\brief An interface for all marker based converter classes.
    A marker based converter maps an input motion to an output motion while assuming that input and output models are markered.
	The main application of marker based converters is to realize
	converters from (e.g. Vicon) Motion Data to an MMM model.

	\see ConverterFactory
*/
class MMM_IMPORT_EXPORT MarkerBasedConverter: public Converter
{
public:
	EIGEN_MAKE_ALIGNED_OPERATOR_NEW

	MarkerBasedConverter(const std::string &name);

	
	/*!
	Setup ViconMarker<->ModelMarker mapping.
	No checks are performed here, the mapping is verfified later.
	*/
	void setMarkerMapping(const std::map<std::string, std::string> &markerMap);


	/*!
	Basic setup of a converter
	\param inputModel Specifies to which model the inputMotion is linked. In case MarkerMotions are used as input (e.g. Vicon->MMM) the input model can be empty.
	\param inputMotion The motion to convert.
	\param outputModel Setup the target model.
	\return true on success.
	*/
	virtual bool setup(ModelPtr inputModel, AbstractMotionPtr inputMotion, ModelPtr outputModel);

	/*!
	Basic setup of a marker based converter
	\param inputMotion The motion to convert.
	\param outputModel Setup the target model.
	\return true on success.
	*/
	virtual bool setup(AbstractMotionPtr inputMotion, ModelPtr outputModel);


	std::map<std::string, std::string> getMarkerMapping() const;

    MarkerMotionPtr getInputMarkerMotion() {return inputMarkerMotion;}

protected:
	//! A casted version of the inputMotion
	MarkerMotionPtr inputMarkerMotion;

	//! The mapping describes which input markers belong to which output markers
	std::map<std::string, std::string> markerMapping;
};

typedef boost::shared_ptr<MarkerBasedConverter> MarkerBasedConverterPtr;

}

#endif 
